#include <arpa/inet.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/stat.h>
#include <sys/sendfile.h>
#include <netinet/in.h>
//#include <netinet/tcp.h>
#include <unistd.h>
#include <fcntl.h>
#include <stdio.h>
#include <errno.h>

//#include "types.h"
#include "guest.h"
//#include "testing.h"

int file_size(int fd) {
  struct stat s;
  fstat(fd, &s);
  
  return s.st_size;
}




int send_test(char *filename) {
  int res, size;
  int fd_in, fd_out;
  
  fd_in = open (filename, O_RDONLY);
  if (fd_in == -1)
    return 1;
  
  fd_out = open (PROC_FILE_PATH, O_WRONLY);
  if (fd_out == -1) {
    close(fd_in);
    return 2;
  }
  
  size = file_size (fd_in);
  
  printf("'%s' size: %d\n", filename, size);
  
  res = sendfile(fd_out, fd_in, 0, size);
  printf("sendfile '%s' -> '%s': %d\n", filename, PROC_FILE_PATH, res);
  res = (res == -1 ? 3 : 0);
  
  close(fd_out);
  close(fd_in);
  
  return res;
}



int test(const char *result_file_name) {
  struct file_info info;
  int res, loop;
  int fd_in, fd_out;
  
  fd_in = open(PROC_FILE_PATH, O_RDWR);
  if (fd_in == -1)
    return 1;
  
  fd_out = open(result_file_name, O_CREAT | O_RDWR, S_IRUSR | S_IWUSR);
  if (fd_out == -1) {
    close(fd_in);
    return 2;
  }
  
  
  loop = 1;
  while (loop) {
    res = read(fd_in, &info, sizeof(info));
    if (res < 0) {
      printf("read info error: %d\n", res);
      break;
    }
    
    loop = !info.result;
    
    res = sendfile(fd_out, fd_in, 0, info.size);
    if (res < 0) {
      printf("senfile error: %d\n", res);
      break;
    }
  }
  
  close(fd_out);
  close(fd_in);
  
  return res < 0 ? 3 : 0;
}


int main(int argc, char *argv[])
{
  if (argc != 3) {
    printf("usage: %s test_file_name result_file_name\n", argv[0]);
    return 1;
  }
  
  int res = send_test(argv[1]);
  
  if (res != 0) {
    printf ("send_test: %d\n", res);
    return 1;
  }
  
  res = test(argv[2]);
  
  if (res != 0) {
    printf ("test: %d\n", res);
    return 1;
  }
  
  return 0;
}